
#ifndef __KEY_H
#define __KEY_H

#include "../iface/debug.h"
#include "../iface/CryptInterface.h"

#define KEY_TYPE_KEY         0
#define KEY_TYPE_PUBLIC_RSA  1
#define KEY_TYPE_PRIVATE_RSA 2
#define KEY_TYPE_PUBLIC_DSA  3
#define KEY_TYPE_PRIVATE_DSA 4
#define KEY_TYPE_SYMM_AES    5
#define KEY_TYPE_SYMM_DES    6

#define KEY_ASYMMETRIC_PAIR_RSA  0
#define KEY_SYMMETRIC_AES        1

#define RSA_BITS 2048
#define AES_BITS 256

class Key
{
   public:
      // Destructor
      virtual ~Key()
      {
         if (keyname) free((void *)keyname);
         keyname = NULL;
      }
      // To import from text - Base64 RAW or PEM
      virtual int ImportKeyFromASCII(const char *text, const char *name) = 0;
      // To export to text - Base64 RAW or PEM
      virtual int ExportKeyToASCII(char **text) = 0;
      // Import from text with password
      virtual int ImportKeyFromASCIIWithPassword(const char *text, const char *password, const char *name) = 0;
      // Export to text with password
      virtual int ExportKeyToASCIIWithPassword(char **text, const char *password) = 0;
      // Is asymmetric key?
      virtual int IsAsymmetricKey() = 0;
      // Get key type
      virtual int GetKeyType() { return KEY_TYPE_KEY; }
      // Get key type name
      virtual const char *GetKeyTypeFullName() { return key_type_names[GetKeyType()]; }
      // Get key type name
      virtual const char *GetKeyTypeAbbrName() { return key_type_abbrs[GetKeyType()]; }
      // Get key name
      virtual const char *GetKeyName() { return keyname; }
      // Set key name
      virtual void SetKeyName(const char *tname)
      {
         if (keyname) free((void *)keyname);
         keyname = (tname) ? (const char *)strdup(tname) : NULL;
      }
   protected:
      const char *keyname;
      static const char *key_type_names[];
      static const char *key_type_abbrs[];
};

class EncryptionKey : public virtual Key
{
   public:
      // Get context
      virtual int GetCryptlibEncryptionContext(CRYPT_CONTEXT *keyContext) = 0;
};

class DecryptionKey : public virtual Key
{
   public:
      // Get context
      virtual int GetCryptlibDecryptionContext(CRYPT_CONTEXT *keyContext) = 0;
};

class SigningKey : public virtual Key
{
   public:
      // Get context
      virtual int GetCryptlibSigningContext(CRYPT_CONTEXT *keyContext) = 0;
};

class CheckingKey : public virtual Key
{
   public:
      // Get context
      virtual int GetCryptlibCheckingContext(CRYPT_CONTEXT *keyContext) = 0;
};

class PublicKey : public virtual Key
{
   public:
      // Compare keys are they equal?
      virtual int CompareKeyEqual(PublicKey *pubkey) = 0;
      // Is asymmetric
      int IsAsymmetricKey() { return 2; }
};

class PrivateKey : public virtual Key
{
   public:
      // Compare keys belonging to same keypair
      virtual int CompareKeyBelongs(PublicKey *pubkey) = 0;
      // Is asymmetric
      int IsAsymmetricKey() { return 1; }
};

class SymmKey : public virtual Key
{
   public:
      // Compare keys are they equal?
      virtual int CompareKeyEqual(SymmKey *symkey) = 0;
      // Is asymmetric
      int IsAsymmetricKey() { return 0; }
};

#endif
